package com.hc.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.hc.common.service.RedisService;
import com.hc.constant.RedisConst;
import com.hc.domain.City;
import com.hc.mapper.CityMapper;
import com.hc.service.CityService;
import org.springframework.cache.annotation.CacheConfig;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.CachePut;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.List;

/**
 * @author hecai
 */
@Service
@CacheConfig(cacheManager = "cacheManager")
public class CityServiceImpl extends ServiceImpl<CityMapper, City> implements CityService {

    /**
     * 用来在redis中缓存：键-市编号，值-省编号
     */
    @Resource
    private RedisService<City> cityRedisServiceImpl;

    /**
     * 用来在redis中缓存：键-省编号，值-省下所有的市
     */
    @Resource
    private RedisService<List<City>> provinceCityRedisServiceImpl;

    @Override
    @CachePut(value = RedisConst.CITY, key = "#city.id", condition = "#flag==true")
    public City insertCity(City city, Boolean flag) {
        int insertRes = baseMapper.insert(city);
        if (insertRes == 1) {
            List<City> cityList = provinceCityRedisServiceImpl.get(RedisConst.PROVINCE_CITY + "::" + city.getProvinceId());
            cityList.add(city);
            //排序
            cityList.sort((item1, item2) -> {
                int t1 = item1.getPriority() == null ? 0 : item1.getPriority();
                int t2 = item2.getPriority() == null ? 0 : item2.getPriority();
                return t2 - t1;
            });
            provinceCityRedisServiceImpl.set(RedisConst.PROVINCE_CITY + "::" + city.getProvinceId(), cityList);
        }

        return city;
    }

    @Override
    @Cacheable(value = RedisConst.CITY, key = "#id", condition = "#flag==true", unless = "#result==null")
    public City findCityById(Integer id, Boolean flag) {
        City city = baseMapper.selectById(id);
        return city;
    }

    @Override
    @Cacheable(value = RedisConst.PROVINCE_CITY, key = "#provinceId", condition = "#flag==true", unless = "#result.size()==0")
    public List<City> findCityByProvinceId(Integer provinceId, Boolean flag) {
        QueryWrapper<City> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("province_id", provinceId);
        List<City> cityList = baseMapper.selectList(queryWrapper);
        return cityList;
    }

    @Override
    @CachePut(value = RedisConst.CITY, key = "#city.id", condition = "#flag==true")
    public City updateCity(City city, Boolean flag) {
        //原City
        City city0 = cityRedisServiceImpl.get(RedisConst.CITY + "::" + city.getId());

        int updateRes = baseMapper.updateById(city);
        //更新后的完整的City
        city = baseMapper.selectById(city.getId());

        if (updateRes == 1) {
            //目标省下的所有City
            List<City> cityList = provinceCityRedisServiceImpl.get(RedisConst.PROVINCE_CITY + "::" + city.getProvinceId());

            //如果原city在目标城市中，即没有换城市
            boolean flag2 = true;
            for (int i = 0; i < cityList.size(); i++) {
                City item = cityList.get(i);
                if (item.getId().equals(city0.getId())) {
                    cityList.set(i, city);
                    flag2 = false;
                    break;
                }
            }
            //排序
            cityList.sort((item1, item2) -> {
                int t1 = item1.getPriority() == null ? 0 : item1.getPriority();
                int t2 = item2.getPriority() == null ? 0 : item2.getPriority();
                return t2 - t1;
            });
            provinceCityRedisServiceImpl.set(RedisConst.PROVINCE_CITY + "::" + city.getProvinceId(), cityList);

            //换城市了
            if (flag2) {
                //原来的城市下的country列表减去
                List<City> cityList0 = provinceCityRedisServiceImpl.get(RedisConst.PROVINCE_CITY + "::" + city0.getProvinceId());
                for (int i = 0; i < cityList0.size(); i++) {
                    if (cityList0.get(i).getId().equals(city0.getId())) {
                        cityList0.remove(i);
                        break;
                    }
                }
                provinceCityRedisServiceImpl.set(RedisConst.PROVINCE_CITY + "::" + city0.getProvinceId(), cityList0);
                //目标城市下的country列表增加
                cityList.add(city);
                //排序
                cityList.sort((item1, item2) -> {
                    int t1 = item1.getPriority() == null ? 0 : item1.getPriority();
                    int t2 = item2.getPriority() == null ? 0 : item2.getPriority();
                    return t2 - t1;
                });
                provinceCityRedisServiceImpl.set(RedisConst.PROVINCE_CITY + "::" + city.getProvinceId(), cityList);
            }
        }
        return city;
    }

    @Override
    @CacheEvict(value = RedisConst.CITY, key = "#id", condition = "#flag==true")
    public City deleteCityById(Integer id, Boolean flag) {
        City city = cityRedisServiceImpl.get("city::" + id);
        if (city != null) {
            List<City> cityList = provinceCityRedisServiceImpl.get(RedisConst.PROVINCE_CITY + "::" + city.getProvinceId());
            for (int i = 0; i < cityList.size(); i++) {
                City item = cityList.get(i);
                if (item.getId().equals(id)) {
                    cityList.remove(i);
                    break;
                }
            }
            provinceCityRedisServiceImpl.set(RedisConst.PROVINCE_CITY + "::" + city.getProvinceId(), cityList);

            baseMapper.deleteById(id);
        }

        return city;
    }
}
